#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "newgamedialog.h"
#include "game.h"
#include "soundsystemfmod.h"
#include "inventorybutton.h"
#include <QDebug>
#include <QPoint>
#include <QList>
#include <QTimer>
#include <QGraphicsItem>


MainWindow::MainWindow(QWidget *parent) :
   QMainWindow(parent),
   ui(new Ui::MainWindow)
{
   ui->setupUi(this);
   connect(ui->colorWheel, SIGNAL(newColorSelected(QColor)), this, SLOT(onNewColor(QColor)));
   connect(ui->inventory, SIGNAL(newSelection(quint32)), this, SLOT(onInvNewSelection(quint32)));
   connect(ui->inventoryTower, SIGNAL(newSelection(quint32)), this, SLOT(onInvTowerSelection(quint32)));
   connect(ui->gameView, SIGNAL(newSelection(ENTITY_TYPE,quint32)), this, SLOT(onGameViewNewSelection(ENTITY_TYPE,quint32)));
   connect(ui->gameView, SIGNAL(placedEntity(ENTITY_TYPE,QPointF,quint32)), this, SLOT(onGameViewPlacedEntity(ENTITY_TYPE,QPointF,quint32)));

   mServer = 0;
   mClient = 0;

   ui->gameView->setMainWindow(this);

   onNewGame();

   onPlaceUnitButton();
   onMuteSound(ui->actionToggle_Mute->isChecked());

   EntityBaseStats s;
   s.type = ENTITY_TOWER;
   s.color = qRgb(255,0,0);
   s.size = 1;
   s.kind = TOWER_BEAM;
   ui->inventoryTower->addButton(TOWER_BEAM, s);
}


MainWindow::~MainWindow()
{
   qDebug() << "~MainWindow";
   if (mClient) delete mClient;
   if (mServer) delete mServer;
   delete ui;
}

void MainWindow::tick()
{
   ui->inventory->tick();
}


void MainWindow::onPlaceTowerButton()
{
/*
   ui->entityKindSlider->setMinimum(TOWER_END-1);
   ui->entityKindSlider->setValue(ui->entityKindSlider->minimum()); // until we get more towers
   ui->entityKindSlider->setDisabled(true);                         // until we get more towers
   ui->entityPreview->setEntityType(ENTITY_TOWER);
   if (ui->inventory->isSelectionModifiable())
   {
      ui->inventory->setSelectionStats(ui->entityPreview->entityStats());
      ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);
   }
*/
}


void MainWindow::onPlaceUnitButton()
{
   ui->entityKindSlider->setMinimum(3);
   ui->entityKindSlider->setDisabled(false);
   ui->entityPreview->setEntityType(ENTITY_UNIT);
   if (ui->inventory->isSelectionModifiable())
   {
      ui->inventory->setSelectionStats(ui->entityPreview->entityStats());
      ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);
   }
}


void MainWindow::onReadyButton()
{
   qDebug() << "READY";
   if (mClient)
      mClient->sendPlayerReady(true);
   //mTimer->start();
   //mGame->start();
}


void MainWindow::onNewGame()
{
   NewGameDialog n(this);
   if (n.exec())
   {
      if (mServer) delete mServer;
      if (mClient) delete mClient;
      if (n.isHost)
      {
         qDebug() << "OnNewGame::Host selected.";
         mServer = new Server(n.hostIP, n.hostPort);
         mClient = new Client();
         mClient->setRender(ui->gameView);
         mClient->sendPlayerJoin(n.hostIP, n.hostPort);
      }
      else
      {
         qDebug() << "OnNewGame::Join selected.";
         mClient = new Client();
         mClient->setRender(ui->gameView);
         mClient->sendPlayerJoin(n.joinIP, n.joinPort);
      }
      connect(mClient, SIGNAL(newSquadID(quint32)), this, SLOT(onNewSquadID(quint32)));
      connect(mClient, SIGNAL(squadRemoved(quint32)), this, SLOT(onSquadRemoved(quint32)));
   }
}


void MainWindow::onEntityKind(int value)
{
   ui->entityPreview->setEntityKind(value);
   // If we set the reset the selected squad, update the cursor
   if (ui->inventory->isSelectionModifiable())
   {
      ui->inventory->setSelectionStats(ui->entityPreview->entityStats());
      ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);
   }
}


void MainWindow::onEntitySize(int value)
{
   ui->entityPreview->setEntitySize(value);
   // If we set the reset the selected squad, update the cursor
   if (ui->inventory->isSelectionModifiable())
   {
      ui->inventory->setSelectionStats(ui->entityPreview->entityStats());
      ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);
   }
}


void MainWindow::onNewColor(QColor color)
{
   if (ui->hudTypeStack->currentIndex()==0)
   {
      ui->entityPreview->setEntityColor(color);
      if (ui->inventory->isSelectionModifiable())
      {
         ui->inventory->setSelectionStats(ui->entityPreview->entityStats());
         ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);
      }
   }
   else
   {
      ui->inventoryTower->setColorForAllButtons(color);
      ui->gameView->updateCursor(ui->inventoryTower->selectionStats(), 1);
   }

}


void MainWindow::onMuteSound(bool value)
{
   qDebug() << "MainWindow::onMuteSound" << value;
   SoundSystemFMOD::instance()->mute(value);
}


void MainWindow::onShowRanges(bool value)
{
   qDebug() << "MainWindow::onShowRanges" << value;
   ui->gameView->setShowRanges(value);
}


void MainWindow::onBlendRanges(bool value)
{
   qDebug() << "MainWindow::onBlendRanges" << value;
   ui->gameView->setBlendRanges(value);
}


void MainWindow::onInvNewSelection(quint32 squadID)
{
   qDebug() << "MainWindow::onInvNewSelection=" << squadID;

   if (squadID > 0)
   {
      EntityBaseStats stats = ui->inventory->selectionStats();
      ui->entityPreview->setEntityStats(stats);

      if (ui->inventory->isSelectionModifiable())
         ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);

      if (stats.type == ENTITY_TOWER)
      {
         ui->entityKindSlider->setMinimum(TOWER_END-1);
         ui->entityKindSlider->setDisabled(true);
      }
      else
      {
         ui->entityKindSlider->setMinimum(3);
         ui->entityKindSlider->setDisabled(false);
      }
      ui->entitySizeSlider->setDisabled(false);

      // Set sliders to selection stats
      ui->entityKindSlider->setValue(stats.kind);
      ui->entitySizeSlider->setValue(stats.size);
   }
   else
   {
      ui->gameView->setSelection(0);
      ui->gameView->clearCursor();
   }
}


void MainWindow::onGameViewNewSelection(ENTITY_TYPE type, quint32 id)
{
   qDebug() << "MainWindow::onGameViewNewSelection id=" << id << "type=" << type;
   if (id == 0)
   {
      ui->inventory->setSelection(id, false);
      ui->inventoryTower->setSelection(0,false);
   }
   else if (type==ENTITY_UNIT)
   {
      ui->inventory->setSelection(id, false);
   }
   else if (type==ENTITY_TOWER)
   {
      ClientEntity *e = mClient->game->entities.value(id);

      if (e)
         ui->towerRangeSlider->setValue(e->base.size);

      // set hud widget values
   }
}

void MainWindow::onGameViewPlacedEntity(ENTITY_TYPE type, QPointF pos, quint32 emitterID)
{
   if (mClient)
   {
      if (type == ENTITY_UNIT && ui->inventory->hasSelection())
      {
         EntitySquadType squad = *ui->inventory->selection();
         mClient->sendEntitySquadAddToEmitter(squad, emitterID);
         ui->inventory->setDisabled(squad.id);
         ui->inventory->setSelection(0);
      }
      else if (type == ENTITY_TOWER && ui->inventoryTower->hasSelection())
      {
         EntitySquadType squad = *ui->inventoryTower->selection();
         squad.size = 1;
         mClient->sendEntityAdd(squad.stats, pos);
         ui->inventoryTower->setSelection(0);
      }

      ui->gameView->clearCursor();
   }
}


void MainWindow::onInvAdd()
{
   mClient->sendEntitySquadIDRequest();
}


void MainWindow::onNewSquadID(quint32 squadID)
{
   ui->gameView->setSelection(0);
   ui->inventory->addButton(squadID, ui->entityPreview->entityStats());
   ui->inventory->setSelection(squadID, false);
   ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);
}


void MainWindow::onInvRemove()
{
   ui->inventory->removeSelection();
}


void MainWindow::onInvInc()
{
   if (ui->inventory->isSelectionModifiable())
   {
      ui->inventory->incSelection();
      ui->gameView->updateCursor(ui->entityPreview->entityStats(), ui->inventory->selection()->size);
   }
}


void MainWindow::onInvDec()
{
   ui->inventory->decSelection();
}


void MainWindow::onSquadRemoved(quint32 squadID)
{
   qDebug() << "MainWindow::onSquadRemoved=" << squadID;
   ui->inventory->setDisabled(squadID, false);
}

void MainWindow::onToggleHud(bool toggle)
{
   qDebug() << "MainWindow::onToggleHud=" << toggle;
   ui->hudTypeStack->setCurrentIndex((int)toggle);
}

void MainWindow::onInvTowerSelection(quint32 id)
{
   qDebug() << "MainWindow::onInvTowerSelection=" << id;
   EntityBaseStats stats = ui->inventoryTower->selectionStats();
   stats.size = ui->towerRangeSlider->value();
   ui->inventoryTower->setSelectionStats(stats);
   ui->gameView->updateCursor(ui->inventoryTower->selectionStats(), 1);
}

void MainWindow::onTowerRange(int value)
{
   //qDebug() << "MainWindow::onTowerRange=" << value;
   if (ui->inventoryTower->hasSelection())
   {
      EntityBaseStats stats = ui->inventoryTower->selectionStats();
      stats.size = value;
      ui->inventoryTower->setSelectionStats(stats);
      ui->gameView->updateCursor(ui->inventoryTower->selectionStats(), 1);
   }

}
